package de.bht.netviz.ipsaver.lookup.dao;

import de.bht.netviz.dao.exceptions.NonexistentEntityException;
import de.bht.netviz.ipsaver.lookup.model.FreeGeoLookupData;
import de.bht.netviz.ipsaver.lookup.model.FreeGeoLookupData_;
import java.io.Serializable;
import java.util.List;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.Query;
import javax.persistence.EntityNotFoundException;
import javax.persistence.TypedQuery;
import javax.persistence.criteria.CriteriaBuilder;
import javax.persistence.criteria.CriteriaQuery;
import javax.persistence.criteria.Predicate;
import javax.persistence.criteria.Root;

/**
 * JPA Controller für Lookupdaten des FreeGeo IP Services.
 * 
 * @author Marius Hentschel
 * @since  2012/11/05
 */
public class FreeGeoLookupDataJpaController implements Serializable, IJpaController {

   public FreeGeoLookupDataJpaController(EntityManagerFactory emf) {
      this.emf = emf;
   }
   private EntityManagerFactory emf = null;

   public EntityManager getEntityManager() {
      return emf.createEntityManager();
   }

   public void create(FreeGeoLookupData freeGepLookupData) {
      EntityManager em = null;
      try {
         em = getEntityManager();
         em.getTransaction().begin();
         em.persist(freeGepLookupData);
         em.getTransaction().commit();
      } finally {
         if (em != null) {
            em.close();
         }
      }
   }

   public void edit(FreeGeoLookupData freeGeoLookupData) throws NonexistentEntityException, Exception {
      EntityManager em = null;
      try {
         em = getEntityManager();
         em.getTransaction().begin();
         freeGeoLookupData = em.merge(freeGeoLookupData);
         em.getTransaction().commit();
      } catch (Exception ex) {
         String msg = ex.getLocalizedMessage();
         if (msg == null || msg.length() == 0) {
            long id = freeGeoLookupData.getId();
            if (findFreeGeoLookupData(id) == null) {
               throw new NonexistentEntityException("The freeGeoLookupData with id " + id + " no longer exists.");
            }
         }
         throw ex;
      } finally {
         if (em != null) {
            em.close();
         }
      }
   }

   public void destroy(long id) throws NonexistentEntityException {
      EntityManager em = null;
      try {
         em = getEntityManager();
         em.getTransaction().begin();
         FreeGeoLookupData freeGeoLookupData;
         try {
            freeGeoLookupData = em.getReference(FreeGeoLookupData.class, id);
            freeGeoLookupData.getId();
         } catch (EntityNotFoundException enfe) {
            throw new NonexistentEntityException("The freeGeoLookupData with id " + id + " no longer exists.", enfe);
         }
         em.remove(freeGeoLookupData);
         em.getTransaction().commit();
      } finally {
         if (em != null) {
            em.close();
         }
      }
   }

   public List<FreeGeoLookupData> findFreeGeoLookupDataEntities() {
      return findFreeGeoLookupDataEntities(true, -1, -1);
   }

   public List<FreeGeoLookupData> findFreeGeoLookupDataEntities(int maxResults, int firstResult) {
      return findFreeGeoLookupDataEntities(false, maxResults, firstResult);
   }

   private List<FreeGeoLookupData> findFreeGeoLookupDataEntities(boolean all, int maxResults, int firstResult) {
      EntityManager em = getEntityManager();
      try {
         CriteriaQuery cq = em.getCriteriaBuilder().createQuery();
         cq.select(cq.from(FreeGeoLookupData.class));
         Query q = em.createQuery(cq);
         if (!all) {
            q.setMaxResults(maxResults);
            q.setFirstResult(firstResult);
         }
         return q.getResultList();
      } finally {
         em.close();
      }
   }

   public FreeGeoLookupData findFreeGeoLookupData(long id) {
      EntityManager em = getEntityManager();
      try {
         return em.find(FreeGeoLookupData.class, id);
      } finally {
         em.close();
      }
   }

   public int getFreeGeoLookupDataCount() {
      EntityManager em = getEntityManager();
      try {
         CriteriaQuery cq = em.getCriteriaBuilder().createQuery();
         Root<FreeGeoLookupData> rt = cq.from(FreeGeoLookupData.class);
         cq.select(em.getCriteriaBuilder().count(rt));
         Query q = em.createQuery(cq);
         return ((Long) q.getSingleResult()).intValue();
      } finally {
         em.close();
      }
   }

   FreeGeoLookupData findByIp(String ip) {
      FreeGeoLookupData retVal = null;
      
      
      CriteriaBuilder qb = this.emf.getCriteriaBuilder();
      CriteriaQuery<FreeGeoLookupData> c = qb.createQuery(FreeGeoLookupData.class);
      Root<FreeGeoLookupData> p = c.from(FreeGeoLookupData.class);
      Predicate condition = qb.equal(p.get(FreeGeoLookupData_.ip), ip);
      c.where(condition);
      TypedQuery<FreeGeoLookupData> q = this.emf.createEntityManager().createQuery(c); 
      List<FreeGeoLookupData> result = q.getResultList();
      
      if( result != null ) {
         switch( result.size() ) {
            case 1:
               retVal = result.get(0);
               break;
            case 0:
            default:
               retVal = null;
         }
      }
      return retVal;
   }
   
}
